package cn.easyplatform.studio.web.views.impl;

import cn.easyplatform.entities.beans.api.ApiBean;
import cn.easyplatform.entities.beans.api.Input;
import cn.easyplatform.lang.Strings;
import cn.easyplatform.studio.StudioApp;
import cn.easyplatform.studio.cmd.biz.QueryAllCmd;
import cn.easyplatform.studio.cmd.identity.UpdateProjectCmd;
import cn.easyplatform.studio.context.Contexts;
import cn.easyplatform.studio.utils.HttpUtils;
import cn.easyplatform.studio.utils.StringUtil;
import cn.easyplatform.studio.utils.WebUtils;
import cn.easyplatform.studio.vos.BizQueryVo;
import cn.easyplatform.studio.vos.FieldVo;
import cn.easyplatform.studio.vos.ResultVo;
import cn.easyplatform.studio.web.editors.Editor;
import cn.easyplatform.studio.web.editors.EditorCallback;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import org.zkoss.util.resource.Labels;
import org.zkoss.zk.ui.Component;
import org.zkoss.zk.ui.Page;
import org.zkoss.zk.ui.event.Event;
import org.zkoss.zk.ui.event.EventListener;
import org.zkoss.zk.ui.event.Events;
import org.zkoss.zk.ui.event.InputEvent;
import org.zkoss.zul.*;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @author 潘凌
 */
public class ApiTestView extends AbstractView<ApiBean> {
    private Vlayout vlayout;
    private Listbox sourcesBox;
    private Textbox urlText;
    private Textbox resultText;
    private Combobox combobox;
    private String baseUrl;
    private String token;
    private String scope;

    /**
     * @param cb
     */
    protected ApiTestView(EditorCallback<ApiBean> cb,String scope) {
        super(cb);
        this.scope = scope;
        if (StudioApp.getAppPath().equals("/ROOT")) {
            baseUrl = StudioApp.getApiTestBaseUrl() + "/";
        } else {
            baseUrl = StudioApp.getApiTestBaseUrl() + StudioApp.getAppPath();
        }
    }

    @Override
    public void doHighlighted() {
        super.doHighlighted();
        win.setWidth("520px");
    }

    /*@Override
    public void doOverlapped() {
        super.doOverlapped();
        win.setWidth("520px");
    }*/

    @Override
    protected void createContent(Component parent) {
        if ("simple".equals(scope))
            initSimpleView(parent);
        else if ("more".equals(scope))
            initMoreView(parent);
    }

    private void initSimpleView(Component parent){
        vlayout = new Vlayout();
        vlayout.setVflex("1");

        Hlayout topHlayout = new Hlayout();
        topHlayout.setStyle("padding:3px");
        topHlayout.setHflex("1");
        combobox = new Combobox();
        combobox.setWidth("80px");
        combobox.setReadonly(true);
        combobox.appendChild(new Comboitem("POST"));
        combobox.appendChild(new Comboitem("GET"));
        combobox.setParent(topHlayout);
        combobox.setSelectedIndex(0);
        combobox.setVisible(false);
        Label label = new Label();
        Div div = new Div();
        div.setStyle("padding-top: 3px;");
        div.setParent(topHlayout);
        //label.setValue("URL:");
        label.setValue("API:");
        label.setParent(div);
        Textbox textbox = new Textbox();
        urlText = textbox;
        textbox.setHflex("1");
        textbox.setParent(topHlayout);
        topHlayout.setParent(vlayout);
        Button btn = new Button(Labels.getLabel("entity.api.test"));
        btn.setId("testBtn");
        btn.setSclass("pull-right");
        btn.setIconSclass("z-icon-check");
        btn.addEventListener(Events.ON_CLICK, this);
        btn.setParent(topHlayout);
        Button clear = new Button(Labels.getLabel("entity.api.clear"));
        clear.setId("clearBtn");
        clear.setSclass("pull-right");
        clear.setIconSclass("z-icon-close");
        clear.addEventListener(Events.ON_CLICK, this);
        clear.setParent(topHlayout);
//        Button more = new Button(Labels.getLabel("entity.api.more"));
//        more.setId("moreBtn");
//        more.setSclass("pull-right");
//        more.setIconSclass("z-icon-link");
//        more.addEventListener(Events.ON_CLICK, new EventListener<Event>() {
//            @Override
//            public void onEvent(Event event) throws Exception {
//                AbstractView.createApiTestView(cb,"more").doHighlighted();
//                vlayout.getRoot().detach();
//            }
//        });
//        more.setParent(topHlayout);

        Vlayout centerVlayout = new Vlayout();
        centerVlayout.setHflex("1");
        centerVlayout.setVflex("1");
        centerVlayout.setStyle("padding-top:3px");

        centerVlayout.appendChild(new Label("Request:"));
        sourcesBox = new Listbox();
        sourcesBox.setHflex("1");
        sourcesBox.setVflex("1");
        //sourcesBox.setCheckmark(true);
        sourcesBox.setMold("paging");
        sourcesBox.setPageSize(20);
        sourcesBox.setParent(centerVlayout);

        Listhead listhead = new Listhead();
        listhead.setSizable(true);
        listhead.setParent(sourcesBox);

        Listheader idListheader = new Listheader();
        idListheader.setLabel("key");
        idListheader.setHflex("2");
        idListheader.setParent(listhead);

        Listheader nameListheader = new Listheader();
        nameListheader.setLabel("value");
        nameListheader.setHflex("3");
        nameListheader.setParent(listhead);

        centerVlayout.setParent(vlayout);
        vlayout.setParent(parent);

        Vlayout bottomVlayout = new Vlayout();
        bottomVlayout.setVflex("1");
        bottomVlayout.setHflex("1");

        bottomVlayout.appendChild(new Label("Result:"));
        Textbox response = new Textbox();
        resultText = response;
        response.setVflex("1");
        response.setHflex("1");
        //response.setRows(6);
        response.setParent(bottomVlayout);

        bottomVlayout.setParent(vlayout);
        redraw();
        urlText.setValue(cb.getValue().getId());
        urlText.setReadonly(true);
    }

    private void initMoreView(Component parent){
        vlayout = new Vlayout();
        vlayout.setVflex("1");

        Hlayout topHlayout = new Hlayout();
        topHlayout.setStyle("padding:3px");
        topHlayout.setHflex("1");
        combobox = new Combobox();
        combobox.setWidth("80px");
        combobox.setReadonly(true);
        combobox.appendChild(new Comboitem("POST"));
        combobox.appendChild(new Comboitem("GET"));
        combobox.setParent(topHlayout);
        combobox.setSelectedIndex(0);
        Label label = new Label();
        Div div = new Div();
        div.setStyle("padding-top: 3px;");
        div.setParent(topHlayout);
        label.setValue("URL:");
        label.setParent(div);
        Textbox textbox = new Textbox();
        urlText = textbox;
        textbox.setHflex("1");
        textbox.setParent(topHlayout);
        topHlayout.setParent(vlayout);
        Button btn = new Button(Labels.getLabel("entity.api.test"));
        btn.setId("testBtn");
        btn.setSclass("pull-right");
        btn.setIconSclass("z-icon-check");
        btn.addEventListener(Events.ON_CLICK, this);
        btn.setParent(topHlayout);
        Button clear = new Button(Labels.getLabel("entity.api.clear"));
        clear.setId("clearBtn");
        clear.setSclass("pull-right");
        clear.setIconSclass("z-icon-close");
        clear.addEventListener(Events.ON_CLICK, this);
        clear.setParent(topHlayout);

        Vlayout centerVlayout = new Vlayout();
        centerVlayout.setHflex("1");
        centerVlayout.setVflex("1");
        centerVlayout.setStyle("padding-top:3px");

        Hlayout h = new Hlayout();
        h.setHflex("1");
        h.appendChild(new Label("Request:"));
        Button btnTop = new Button(Labels.getLabel("button.create") + Labels.getLabel("button.property"));
        btnTop.setSclass("pull-right");
        btnTop.setIconSclass("z-icon-plus");
        btnTop.addEventListener(Events.ON_CLICK, new EventListener<Event>() {
            @Override
            public void onEvent(Event event) throws Exception {
                List<Listitem> items = sourcesBox.getItems();
                Listitem ti = new Listitem();
                Listcell listcell1 = new Listcell();
                Textbox textbox1 = new Textbox();
                textbox1.setHflex("1");
                textbox1.setStyle("margin-left:3px");
                listcell1.appendChild(textbox1);
                Listcell listcell2 = new Listcell();
                final Textbox textbox2 = new Textbox();
                textbox2.setHflex("1");
                textbox2.setStyle("margin:3px");
                listcell2.appendChild(textbox2);
                ti.appendChild(listcell1);
                ti.appendChild(listcell2);
                items.add(ti);
            }
        });
        btnTop.setParent(h);
        Button btnTopRe = new Button(Labels.getLabel("button.remove") + Labels.getLabel("button.property"));
        btnTopRe.setSclass("pull-right");
        btnTopRe.setIconSclass("z-icon-minus");
        btnTopRe.addEventListener(Events.ON_CLICK, new EventListener<Event>() {
            @Override
            public void onEvent(Event event) throws Exception {
                if (sourcesBox.getSelectedItem() == null) {
                    WebUtils.showError(Labels.getLabel("editor.select", new String[]{Labels.getLabel("entity.list")}));
                    return;
                }
                Listitem listitem = sourcesBox.getSelectedItem();
                sourcesBox.getItems().remove(listitem);
            }
        });
        btnTopRe.setParent(h);
        centerVlayout.appendChild(h);

        sourcesBox = new Listbox();
        sourcesBox.setHflex("1");
        sourcesBox.setVflex("1");
        sourcesBox.setCheckmark(true);
        sourcesBox.setMold("paging");
        sourcesBox.setPageSize(20);
        sourcesBox.setParent(centerVlayout);

        Listhead listhead = new Listhead();
        listhead.setSizable(true);
        listhead.setParent(sourcesBox);

        Listheader idListheader = new Listheader();
        idListheader.setLabel("key");
        idListheader.setHflex("2");
        idListheader.setParent(listhead);

        Listheader nameListheader = new Listheader();
        nameListheader.setLabel("value");
        nameListheader.setHflex("3");
        nameListheader.setParent(listhead);

        centerVlayout.setParent(vlayout);
        vlayout.setParent(parent);

        Vlayout bottomVlayout = new Vlayout();
        bottomVlayout.setVflex("1");
        bottomVlayout.setHflex("1");

        bottomVlayout.appendChild(new Label("Result:"));
        Textbox response = new Textbox();
        resultText = response;
        response.setVflex("1");
        response.setHflex("1");
        //response.setRows(6);
        response.setParent(bottomVlayout);

        bottomVlayout.setParent(vlayout);
    }


    /**
     * api 初始化
     *
     * @return
     */
    private void init() {

        BizQueryVo vo = new BizQueryVo();
        vo.setId(cb.getValue().getSubType());
        vo.setSearchField("type");
        vo.setSql("SELECT userId,password FROM sys_user_info");
        vo.setParams(new FieldVo[0]);
        vo.setSearchValue("-1");

        //查询api用户
        ResultVo userInfo = StudioApp.execute(new QueryAllCmd(vo));

        //如果不存在,提示用户添加
        if(userInfo.getData()==null || userInfo.getData().size() == 0){
            WebUtils.showError(Labels.getLabel("entity.api.user.empty"));
            return;
        }
        vo = new BizQueryVo();
        vo.setId(cb.getValue().getSubType());
        vo.setSearchField("userId");
        vo.setSql("SELECT orgId FROM sys_user_org_info");
        vo.setParams(new FieldVo[0]);
        vo.setSearchValue(userInfo.getData().get(0)[0] + "");

        //查询用户所属机构
        ResultVo orgInfo = StudioApp.execute(new QueryAllCmd(vo));

        //如果不存在,提示用户添加
        if(userInfo.getData()==null || orgInfo.getData() == null || orgInfo.getData().size() == 0){
            WebUtils.showError(Labels.getLabel("entity.api.org.empty"));
            return;
        }
        JSONObject json = new JSONObject();
        json.put("serviceId", Contexts.getProject().getId());
        //json.put("serviceId", "officialwebsite");
        json.put("orgId", orgInfo.getData().get(0)[0]);
        json.put("nodeId", userInfo.getData().get(0)[0]);
        json.put("nodePass", userInfo.getData().get(0)[1]);
        HttpUtils.getInstance().requestPostJsonAllUrl(baseUrl + "/api/init", json.toJSONString(), new HttpUtils.OnMessageListener() {
            @Override
            public void onMessage(String result) {
                if (Strings.isBlank(result)) {
                    WebUtils.showError("EP服务器连接异常！");
                } else {
                    JSONObject data = JSON.parseObject(result);
                    if ("0000".equals(data.getString("code"))) {
                        token = JSONObject.parseObject(result).getString("data");
                    } else {
                        WebUtils.showError("EP服务器连接失败:" + result);
                    }
                }
            }
        });
    }

    /**
     * 关闭连接
     */
    private void close() {
        JSONObject json = new JSONObject();
        json.put("token", token);
        HttpUtils.getInstance().requestPostJsonAllUrl(baseUrl + "/api/close", json.toJSONString(), new HttpUtils.OnMessageListener() {
            @Override
            public void onMessage(String result) {
                if (Strings.isBlank(result)) {
                    WebUtils.showError("断开EP服务器异常！");
                } else {
                    JSONObject data = JSON.parseObject(result);
                    if ("0000".equals(data.getString("code"))) {
                        token = "";
                    } else {
                        WebUtils.showError("断开EP服务器失败:" + result);
                    }
                }
            }
        });
    }


    private void redraw() {
        createTables(cb.getValue());
    }

    private void createTables(ApiBean apiBean) {
        List<Listitem> items = sourcesBox.getItems();
        if (apiBean.getInputs() != null) {
            for (Input input : apiBean.getInputs()) {
                Listitem ti = new Listitem();
                Listcell listcell1 = new Listcell(input.getName());
                Listcell listcell2 = new Listcell();
                Textbox textbox2 = new Textbox();
                textbox2.setHflex("1");
                textbox2.setStyle("margin:3px");
                listcell2.appendChild(textbox2);
                ti.appendChild(listcell1);
                ti.appendChild(listcell2);
                items.add(ti);
            }
        }
    }

    @Override
    public void onEvent(Event event) throws Exception {
        if (event.getTarget().getId().equals("testBtn"))
            test();
        if (event.getTarget().getId().equals("clearBtn")) {
            for (Listitem listitem : sourcesBox.getItems()) {
                ((Textbox) listitem.getLastChild().getLastChild()).setValue("");
            }
            resultText.setValue("");
        }
    }

    private void test() {
        resultText.setValue("");
        if (Strings.isBlank(urlText.getValue()))
            return;
        Map<String, String> params = new HashMap<>();
        for (Listitem listitem : sourcesBox.getItems()) {
            String keyStr = "";
            if (listitem.getFirstChild().getFirstChild() == null) {
                keyStr = ((Listcell) listitem.getFirstChild()).getLabel();
            } else {
                keyStr = ((Textbox) listitem.getFirstChild().getFirstChild()).getValue();
            }
            String valueStr = ((Textbox) listitem.getLastChild().getLastChild()).getValue();
            if (!Strings.isBlank(valueStr))
                params.put(keyStr, valueStr);
        }
        if ("simple".equals(scope)){
            init();
            if (Strings.isBlank(token))
                return;
            JSONObject json = new JSONObject();
            JSONObject data = new JSONObject();
            for (Map.Entry<String, String> e : params.entrySet()) {
                data.put(e.getKey(), e.getValue());
            }
            if (data != null) {
                if (data.containsKey("role")) {
                    json.put("role", data.getString("role"));
                }
                if (data.containsKey("startNo")) {
                    json.put("startNo", data.getString("startNo"));
                }
                if (data.containsKey("pageSize")) {
                    json.put("pageSize", data.getString("pageSize"));
                }
                if (data.containsKey("processCode")) {
                    json.put("processCode", data.getString("processCode"));
                }
                if (data.containsKey("user")) {
                    json.put("user", data.getString("user"));
                }
            }
            json.put("token", token);
            json.put("id", cb.getValue().getId());
            json.put("data", data);
            HttpUtils.getInstance().requestPostJsonAllUrl(baseUrl + "/api/task", json.toJSONString(), new HttpUtils.OnMessageListener() {
                @Override
                public void onMessage(String result) {
                    resultText.setValue(result);
                }
            });
            close();
            return;
        }
        if ("more".equals(scope)){
            if (combobox.getValue().equals("POST")) {
                HttpUtils.getInstance().requestPostFormAllUrl(urlText.getValue(), params, new HttpUtils.OnMessageListener() {

                    @Override
                    public void onMessage(String result) {
                        resultText.setValue(result);
                    }
                });
            } else if (combobox.getValue().equals("GET")) {
                StringBuffer sb = new StringBuffer();
                if (params != null) {
                    for (Map.Entry<String, String> e : params.entrySet()) {
                        sb.append(e.getKey());
                        sb.append("=");
                        sb.append(e.getValue());
                        sb.append("&");
                    }
                    if (sb.length() != 0)
                        sb.substring(0, sb.length() - 1);
                }
                String url;
                if (sb.length() != 0)
                    url = urlText.getValue() + "?" + sb.toString();
                else
                    url = urlText.getValue();
                HttpUtils.getInstance().requestGetAllUrl(url, new HttpUtils.OnMessageListener() {

                    @Override
                    public void onMessage(String result) {
                        resultText.setValue(result);
                    }
                });
            }
        }
    }

}
